<?php

/**
 * Description of class RechtBitfield
 * 
 * @version 0.1
 * @author Sander van Belleghem
 * 
 */

class RechtBitfield {
    
    private $bitfield = '';
    
    public function __construct(){
        
    }
    
    public function RechtBitfield(){
        
    }
    
    /**
     * addRecht()
     * 
     * @param int $recht_positie is positie in het bitfield van 1-65. 
     * 
     */
    public function addRecht($recht_positie){
        $this->checkRecht($recht_positie);
        
        // Van integer bit maken
        $recht = 1 << ($recht_positie -1);
        
        $this->bitfield |= $recht;
                
        return true;
    }
    
    /**
     * addRechten()
     * 
     * @param array $recht_array
     * @return bool FALSE Functie addRecht returnd false
     *              TRUE Rechten zijn in bitfield geshift
     * 
     */
    public function addRechten($recht_array){       
        foreach($recht_array as $idx => $recht_pos){
            
            if( !$this->addRecht($recht_pos)){
                return false;
            }
        } 
        
        return true;
    }    
    
    /**
     * getBitfield()
     * 
     * @return $this->bitfield Opgegeven bitfield binnen de klasse
     * 
     */
    public function getBitfield(){
        
        return $this->bitfield;
    }
    
    /**
     * heeftRechten()
     * 
     * @param array $recht_array
     * @return bool FALSE if one or more rights are not set in class bitfield<br />
     *              TRUE if all rights are set in class bitfield
     * 
     */
    public function heeftRecht($recht_positie){        
        try{
            $this->checkRecht($recht_positie);

            if($this->bitfield & (1 << ($recht_positie -1))){
                                
                return true;
            }
        } catch (Exception $e){
            throw new Exception('Invalid Recht Positie.');
            trigger_error($e->getMessage());
        }
        return false;
    }
    
    /**
     * heeftRechten()
     * 
     * @param array $recht_array
     * @return bool FALSE if one or more rights are not set in class bitfield<br />
     *              TRUE if all rights are set in class bitfield
     * 
     */
    public function heeftRechten($recht_array){
        
        foreach($recht_array as $idx => $recht_pos){
            if( !$this->heeftRecht($recht_pos)){
                return false;
            }
        }    
        return true;
    }
    
    /**
     * setBitfield()
     * 
     * @param type $bitfield
     * 
     */
    public function setBitfield($bitfield){
        
        if(!empty($bitfield)){  
                        
            $this->bitfield = $bitfield;
        }
    }   
    
    /**
     * checkRecht()
     * 
     * Functie om te controleren of opgegeven recht niet leeg is en binnen de gestelde range is.
     * 
     * @param type $recht_positie
     * @throws Exception Als bit buiten bitfield range is.
     * 
     */
    private function checkRecht($recht_positie){
        
        if(empty($recht_positie) || ($recht_positie > 65  /* 65 is het max van de bit */)){
            throw new Exception('Invalid Recht Positie.');
        }
    }

    /**
     * removeRecht()
     * 
     * Functie om een recht te verwijderen
     * 
     * @param type $recht_positie
     * 
     */    
    public function removeRecht($recht_positie){
        try{
            $this->checkRecht($recht_positie);

            if($this->bitfield & (1 << ($recht_positie -1))){

                $this->bitfield = ~$this->bitfield;

                if($this->bitfield |= 1 << ($recht_positie -1)){
                    
                    $this->bitfield = ~$this->bitfield;
                }
            }
        } catch (Exception $e){
            trigger_error($e->getMessage());
        }
        return false;
    }
}

class TestRechtBitfield {
    public function TestRechtBitfield(){
        try{
            $test = new RechtBitfield();
            $test->addRecht(1);
            $test->addRecht(4);
            $test->addRecht(6);
            $test->removeRecht(4);
                        
            echo "<pre>";
            var_dump($test);
            echo "</pre>";
            
        } catch (Exception $e) {
            echo "<pre>";
            echo $e->getTraceAsString();
            echo "</pre>";
            trigger_error($e->getMessage());
        }
    }
}
?>
